1 <?php
2     $currDir = dirname(__FILE__);
3     require(
"{$currDir}/incCommon.php");
4     $GLOBALS[
'page_title'] = $Translation['view or rebuild fields'];
5     include(
"{$currDir}/incHeader.php");
6
7     
/*
8         $schema: [ tablename => [ fieldname => [ appgini =>
'...', 'db' => '...'], ... ], ... ]
9     */

10
11     
/* application schema as created in AppGini */
12     $schema = array(
13         
'schools' => array(
14             
'id' => array('appgini' => 'INT unsigned not null primary key auto_increment '),
15             
'name' => array('appgini' => 'VARCHAR(40) not null ')
16         ),
17         
'departments' => array(
18             
'id' => array('appgini' => 'INT unsigned not null primary key auto_increment '),
19             
'name' => array('appgini' => 'VARCHAR(40) not null '),
20             
'school' => array('appgini' => 'INT unsigned not null ')
21         ),
22         
'class_time_table' => array(
23             
'id' => array('appgini' => 'INT unsigned not null primary key auto_increment '),
24             
'day' => array('appgini' => 'VARCHAR(40) not null '),
25             
'time_start' => array('appgini' => 'TIME not null '),
26             
'time_end' => array('appgini' => 'TIME not null '),
27             
'unit_code' => array('appgini' => 'VARCHAR(40) not null '),
28             
'venue' => array('appgini' => 'VARCHAR(40) not null '),
29             
'school' => array('appgini' => 'INT unsigned not null '),
30             
'department' => array('appgini' => 'INT unsigned not null '),
31             
'year_of_study' => array('appgini' => 'VARCHAR(40) not null ')
32         ),
33         
'exam_time_table' => array(
34             
'id' => array('appgini' => 'INT unsigned not null primary key auto_increment '),
35             
'date' => array('appgini' => 'DATE not null '),
36             
'time_start' => array('appgini' => 'TIME not null '),
37             
'time_end' => array('appgini' => 'TIME not null '),
38             
'unit_code' => array('appgini' => 'VARCHAR(40) not null '),
39             
'venue' => array('appgini' => 'VARCHAR(40) not null '),
40             
'school' => array('appgini' => 'INT unsigned not null '),
41             
'department' => array('appgini' => 'INT unsigned not null '),
42             
'year_of_study' => array('appgini' => 'VARCHAR(40) not null ')
43         ),
44         
'personal_time_table' => array(
45             
'id' => array('appgini' => 'INT unsigned not null primary key auto_increment '),
46             
'day' => array('appgini' => 'VARCHAR(40) not null '),
47             
'time_start' => array('appgini' => 'TIME not null '),
48             
'time_end' => array('appgini' => 'TIME not null '),
49             
'activity' => array('appgini' => 'VARCHAR(40) not null ')
50         ),
51         
'student_details' => array(
52             
'id' => array('appgini' => 'INT unsigned not null primary key auto_increment '),
53             
'full_name' => array('appgini' => 'VARCHAR(40) not null '),
54             
'school' => array('appgini' => 'INT unsigned not null '),
55             
'department' => array('appgini' => 'INT unsigned not null '),
56             
'year_of_study' => array('appgini' => 'VARCHAR(40) not null '),
57             
'reg_no' => array('appgini' => 'VARCHAR(40) not null unique ')
58         ),
59         
'notices' => array(
60             
'id' => array('appgini' => 'INT unsigned not null primary key auto_increment '),
61             
'notice' => array('appgini' => 'TEXT not null '),
62             
'school' => array('appgini' => 'INT unsigned not null '),
63             
'department' => array('appgini' => 'INT unsigned not null '),
64             
'year_of_study' => array('appgini' => 'VARCHAR(40) not null '),
65             
'date' => array('appgini' => 'DATE ')
66         )
67     );
68
69     $table_captions = getTableList();
70
71     
/* function for preparing field definition for comparison */
72     function prepare_def($def){
73         $def = trim($def);
74         $def = strtolower($def);
75
76         
/* ignore length for int data types */
77         $def = preg_replace(
'/int\w*\([0-9]+\)/', 'int', $def);
78
79         
/* make sure there is always a space before mysql words */
80         $def = preg_replace(
'/(\S)(unsigned|not null|binary|zerofill|auto_increment|default)/', '$1 $2', $def);
81
82         
/* treat 0.000.. same as 0 */
83         $def = preg_replace(
'/([0-9])*\.0+/', '$1', $def);
84
85         
/* treat unsigned zerofill same as zerofill */
86         $def = str_ireplace(
'unsigned zerofill', 'zerofill', $def);
87
88         
/* ignore zero-padding for date data types */
89         $def = preg_replace(
"/date\s*default\s*'([0-9]{4})-0?([1-9])-0?([1-9])'/i", "date default '$1-$2-$3'", $def);
90
91         
return $def;
92     }
93
94     
/**
95      * @brief creates/fixes given field according to given schema
96      * @
return integer: 0 = error, 1 = field updated, 2 = field created
97      */

98     function fix_field($fix_table, $fix_field, $schema, &$qry){
99         
if(!isset($schema[$fix_table][$fix_field])) return 0;
100
101         $def = $schema[$fix_table][$fix_field];
102         $field_added = $field_updated =
false;
103         $eo[
'silentErrors'] = true;
104
105         
// field exists?
106         $res = sql(
"show columns from `{$fix_table}` like '{$fix_field}'", $eo);
107         
if($row = db_fetch_assoc($res)){
108             
// modify field
109             $qry =
"alter table `{$fix_table}` modify `{$fix_field}` {$def['appgini']}";
110             sql($qry, $eo);
111
112             
// remove unique from db if necessary
113             
if($row['Key'] == 'UNI' && !stripos($def['appgini'], ' unique')){
114                 
// retrieve unique index name
115                 $res_unique = sql(
"show index from `{$fix_table}` where Column_name='{$fix_field}' and Non_unique=0", $eo);
116                 
if($row_unique = db_fetch_assoc($res_unique)){
117                     $qry_unique =
"drop index `{$row_unique['Key_name']}` on `{$fix_table}`";
118                     sql($qry_unique, $eo);
119                     $qry .=
";\n{$qry_unique}";
120                 }
121             }
122
123             
return 1;
124         }
125
126         
// create field
127         $qry =
"alter table `{$fix_table}` add column `{$fix_field}` {$schema[$fix_table][$fix_field]['appgini']}";
128         sql($qry, $eo);
129         
return 2;
130     }
131
132     
/* process requested fixes */
133     $fix_table = (isset($_GET[
't']) ? $_GET['t'] : false);
134     $fix_field = (isset($_GET[
'f']) ? $_GET['f'] : false);
135     $fix_all = (isset($_GET[
'all']) ? true : false);
136
137     
if($fix_field && $fix_table) $fix_status = fix_field($fix_table, $fix_field, $schema, $qry);
138
139     
/* retrieve actual db schema */
140     
foreach($table_captions as $tn => $tc){
141         $eo[
'silentErrors'] = true;
142         $res = sql(
"show columns from `{$tn}`", $eo);
143         
if($res){
144             
while($row = db_fetch_assoc($res)){
145                 
if(!isset($schema[$tn][$row['Field']]['appgini'])) continue;
146                 $field_description = strtoupper(str_replace(
' ', '', $row['Type']));
147                 $field_description = str_ireplace(
'unsigned', ' unsigned', $field_description);
148                 $field_description = str_ireplace(
'zerofill', ' zerofill', $field_description);
149                 $field_description = str_ireplace(
'binary', ' binary', $field_description);
150                 $field_description .= ($row[
'Null'] == 'NO' ? ' not null' : '');
151                 $field_description .= ($row[
'Key'] == 'PRI' ? ' primary key' : '');
152                 $field_description .= ($row[
'Key'] == 'UNI' ? ' unique' : '');
153                 $field_description .= ($row[
'Default'] != '' ? " default '" . makeSafe($row['Default']) . "'" : '');
154                 $field_description .= ($row[
'Extra'] == 'auto_increment' ? ' auto_increment' : '');
155
156                 $schema[$tn][$row[
'Field']]['db'] = '';
157                 
if(isset($schema[$tn][$row['Field']])){
158                     $schema[$tn][$row[
'Field']]['db'] = $field_description;
159                 }
160             }
161         }
162     }
163
164     
/* handle fix_all request */
165     
if($fix_all){
166         
foreach($schema as $tn => $fields){
167             
foreach($fields as $fn => $fd){
168                 
if(prepare_def($fd['appgini']) == prepare_def($fd['db'])) continue;
169                 fix_field($tn, $fn, $schema, $qry);
170             }
171         }
172
173         redirect(
'admin/pageRebuildFields.php');
174         exit;
175     }
176 ?>
177
178 <?php
if($fix_status == 1 || $fix_status == 2){ ?>
179     <div
class="alert alert-info alert-dismissable">
180         <button type=
"button" class="close" data-dismiss="alert" aria-hidden="true">&times;</button>
181         <i
class="glyphicon glyphicon-info-sign"></i>
182         <?php
183             $originalValues = array(
'<ACTION>', '<FIELD>', '<TABLE>', '<QUERY>');
184             $action = ($fix_status ==
2 ? 'create' : 'update');
185             $replaceValues = array($action, $fix_field, $fix_table, $qry);
186             echo str_replace($originalValues, $replaceValues, $Translation[
'create or update table']);
187         ?>
188     </div>
189 <?php } ?>
190
191 <div
class="page-header"><h1>
192     <?php echo $Translation[
'view or rebuild fields'] ; ?>
193     <button type=
"button" class="btn btn-default" id="show_deviations_only"><i class="glyphicon glyphicon-eye-close"></i> <?php echo $Translation['show deviations only'] ; ?></button>
194     <button type=
"button" class="btn btn-default hidden" id="show_all_fields"><i class="glyphicon glyphicon-eye-open"></i> <?php echo $Translation['show all fields'] ; ?></button>
195 </h1></div>
196
197 <p
class="lead"><?php echo $Translation['compare tables page'] ; ?></p>
198
199 <div
class="alert summary"></div>
200 <table
class="table table-responsive table-hover table-striped">
201     <thead><tr>
202         <th></th>
203         <th><?php echo $Translation[
'field'] ; ?></th>
204         <th><?php echo $Translation[
'AppGini definition'] ; ?></th>
205         <th><?php echo $Translation[
'database definition'] ; ?></th>
206         <th id=
"fix_all"></th>
207     </tr></thead>
208
209     <tbody>
210     <?php
foreach($schema as $tn => $fields){ ?>
211         <tr
class="text-info"><td colspan="5"><h4 data-placement="left" data-toggle="tooltip" title="<?php echo str_replace ( "<TABLENAME>" , $tn , $Translation['table name title']) ; ?>"><i class="glyphicon glyphicon-th-list"></i> <?php echo $table_captions[$tn]; ?></h4></td></tr>
212         <?php
foreach($fields as $fn => $fd){ ?>
213             <?php $diff = ((prepare_def($fd[
'appgini']) == prepare_def($fd['db'])) ? false : true); ?>
214             <?php $no_db = ($fd[
'db'] ? false : true); ?>
215             <tr
class="<?php echo ($diff ? 'warning' : 'field_ok'); ?>">
216                 <td><i
class="glyphicon glyphicon-<?php echo ($diff ? 'remove text-danger' : 'ok text-success'); ?>"></i></td>
217                 <td><?php echo $fn; ?></td>
218                 <td
class="<?php echo ($diff ? 'bold text-success' : ''); ?>"><?php echo $fd['appgini']; ?></td>
219                 <td
class="<?php echo ($diff ? 'bold text-danger' : ''); ?>"><?php echo thisOr($fd['db'], $Translation['does not exist']); ?></td>
220                 <td>
221                     <?php
if($diff && $no_db){ ?>
222                         <a href=
"pageRebuildFields.php?t=<?php echo $tn; ?>&f=<?php echo $fn; ?>" class="btn btn-success btn-xs btn_create" data-toggle="tooltip" data-placement="top" title="<?php echo $Translation['create field'] ; ?>"><i class="glyphicon glyphicon-plus"></i> <?php echo $Translation['create it'] ; ?></a>
223                     <?php }elseif($diff){ ?>
224                         <a href=
"pageRebuildFields.php?t=<?php echo $tn; ?>&f=<?php echo $fn; ?>" class="btn btn-warning btn-xs btn_update" data-toggle="tooltip" title="<?php echo $Translation['fix field'] ; ?>"><i class="glyphicon glyphicon-cog"></i> <?php echo $Translation['fix it'] ; ?></a>
225                     <?php } ?>
226                 </td>
227             </tr>
228         <?php } ?>
229     <?php } ?>
230     </tbody>
231 </table>
232 <div
class="alert summary"></div>
233
234 <style>
235     .bold{ font-weight: bold; }
236     [data-toggle=
"tooltip"]{ display: block !important; }
237 </style>
238
239 <script>
240     $j(function(){
241         $j(
'[data-toggle="tooltip"]').tooltip();
242
243         $j(
'#show_deviations_only').click(function(){
244             $j(
this).addClass('hidden');
245             $j(
'#show_all_fields').removeClass('hidden');
246             $j(
'.field_ok').hide();
247         });
248
249         $j(
'#show_all_fields').click(function(){
250             $j(
this).addClass('hidden');
251             $j(
'#show_deviations_only').removeClass('hidden');
252             $j(
'.field_ok').show();
253         });
254
255         $j(
'.btn_update, #fix_all').click(function(){
256             
return confirm("<?php echo $Translation['field update warning'] ; ?>");
257         });
258
259         
var count_updates = $j('.btn_update').length;
260         
var count_creates = $j('.btn_create').length;
261         
if(!count_creates && !count_updates){
262             $j(
'.summary').addClass('alert-success').html("<?php echo $Translation['no deviations found'] ; ?>");
263         }
else{
264             
var fieldsCount = "<?php echo $Translation['error fields']; ?>";
265             fieldsCount = fieldsCount.replace(/<CREATENUM>/, count_creates ).replace(/<UPDATENUM>/, count_updates);
266
267
268             $j(
'.summary')
269                 .addClass(
'alert-warning')
270                 .html(
271                     fieldsCount +
272                     
'<br><br>' +
273                     
'<a href="pageBackupRestore.php" class="alert-link">' +
274                         
'<b><?php echo addslashes($Translation['backup before fix']); ?></b>' +
275                     
'</a>'
276                 );
277
278             $j(
'<a href="pageRebuildFields.php?all=1" class="btn btn-danger btn-block"><i class="glyphicon glyphicon-cog"></i> <?php echo addslashes($Translation['fix all']); ?></a>').appendTo('#fix_all');
279         }
280     });
281 </script>
282
283 <?php
284     include(
"{$currDir}/incFooter.php");
285 ?>



Hệ thống xếp lịch học tín chỉ cho sinh viên CNTT trên PHP & MySQL 112.145 lượt xem

Gõ tìm kiếm nhanh...